﻿namespace FiftyOne.Foundation.Mobile.Detection.Wurfl.Matchers
{
    using FiftyOne.Foundation.Mobile.Detection.Wurfl;
    using FiftyOne.Foundation.Mobile.Detection.Wurfl.Handlers;
    using System;
    using System.Collections.Generic;
    using System.Threading;

    internal abstract class Request
    {
        protected AutoResetEvent _completeEvent;
        private FiftyOne.Foundation.Mobile.Detection.Wurfl.Handlers.Handler _handler;
        protected int _inProcess;
        protected Queue<DeviceInfo> _queue;
        protected string _userAgent;

        internal Request(string userAgent, FiftyOne.Foundation.Mobile.Detection.Wurfl.Handlers.Handler handler)
        {
            this._inProcess = 0;
            this._handler = null;
            this._userAgent = userAgent;
            this._queue = CreateQueue(handler);
            this._handler = handler;
        }

        internal Request(string userAgent, FiftyOne.Foundation.Mobile.Detection.Wurfl.Handlers.Handler handler, AutoResetEvent completeEvent)
        {
            this._inProcess = 0;
            this._handler = null;
            this._userAgent = userAgent;
            this._queue = CreateQueue(handler);
            this._handler = handler;
            this._completeEvent = completeEvent;
        }

        internal void Complete()
        {
            lock (this._queue)
            {
                this._inProcess--;
                if (((this._inProcess == 0) && (this._completeEvent != null)) && (this._queue.Count == 0))
                {
                    this._completeEvent.Set();
                }
            }
        }

        private static Queue<DeviceInfo> CreateQueue(FiftyOne.Foundation.Mobile.Detection.Wurfl.Handlers.Handler handler)
        {
            Queue<DeviceInfo> queue = new Queue<DeviceInfo>(handler.UserAgents.Count);
            lock (handler.UserAgents)
            {
                foreach (DeviceInfo[] infoArray in handler.UserAgents)
                {
                    foreach (DeviceInfo info in infoArray)
                    {
                        queue.Enqueue(info);
                    }
                }
            }
            return queue;
        }

        internal DeviceInfo Next()
        {
            DeviceInfo info = null;
            lock (this._queue)
            {
                if (this._queue.Count > 0)
                {
                    this._inProcess++;
                    info = this._queue.Dequeue();
                }
            }
            return info;
        }

        internal int Count
        {
            get
            {
                return this._queue.Count;
            }
        }

        internal virtual FiftyOne.Foundation.Mobile.Detection.Wurfl.Handlers.Handler Handler
        {
            get
            {
                return this._handler;
            }
        }

        internal int InProcess
        {
            get
            {
                return this._inProcess;
            }
        }

        internal string UserAgent
        {
            get
            {
                return this._userAgent;
            }
        }
    }
}

